package com.rfid.row;

import java.io.IOException;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;

import com.rfid.RFIDCaller;
import com.rfid.jni.JNI_RFIDCaller;
import com.rfid.row.convertUtil.ConvertUtils;
import com.rfid.row.convertUtil.ParserXml;

public class RFIDRoWImpl implements RFIDRoW{
	
	private static Map<String,Integer[]> definePatternMap = new HashMap<String, Integer[]>();
	
	private Field field = null;
	private Method setMethod = null;
	private Method getMethod = null;
	private String setMethodName = null;
	private String getMethodName = null;
	private String fieldName = null;
	private String fieldValue = null;
	
	public RFIDRoWImpl() {
		definePatternMap = ParserXml.map;
	}
	
	@Override
	public Object readObject(Class<?> clazz) throws Exception {
		RFIDCaller call = new JNI_RFIDCaller();
		Object object = clazz.newInstance();

		for(Map.Entry<String, Integer[]> entry : definePatternMap.entrySet()) {
			fieldName = entry.getKey();
			field = clazz.getDeclaredField(fieldName);
			setMethodName = "set"+fieldName.toUpperCase().substring(0, 1) + fieldName.substring(1);
			setMethod = clazz.getDeclaredMethod(setMethodName, field.getType());
			Integer[] areas = entry.getValue();
			fieldValue = call.read(areas[0], areas[1]);
			setMethod.invoke(object, ConvertUtils.convert(fieldValue, field.getType()));
		}
		return object;
	}

	public void writeObject(Object object) throws IOException, InstantiationException, IllegalAccessException, SecurityException, NoSuchFieldException, NoSuchMethodException, IllegalArgumentException, InvocationTargetException{
		RFIDCaller call = new JNI_RFIDCaller();
		Class<? extends Object> clazz = object.getClass();
		
		for(Map.Entry<String, Integer[]> entry : definePatternMap.entrySet()) {
			fieldName = entry.getKey();
			getMethodName = "get" + fieldName.toUpperCase().substring(0, 1) + fieldName.substring(1);
			getMethod = clazz.getDeclaredMethod(getMethodName, new Class<?>[]{});
			fieldValue = getMethod.invoke(object, new Object[]{}).toString();
			Integer[] areas = entry.getValue();
			call.write(areas[0], areas[1], fieldValue);
		}
	}

	@Override
	public Object readObjectbyId(Class<?> clazz, int id) throws Exception {
		return null;
	}
}
